﻿using AbpVnext_Module.Dto;
using AbpVnext_Module.Model;
using Microsoft.EntityFrameworkCore;
using System.Collections.Generic;
using System;
using System.Linq;
using System.Linq.Dynamic.Core;
using System.Xml.Linq;
using Volo.Abp.DependencyInjection;
using Volo.Abp.Domain.Repositories.EntityFrameworkCore;
using Volo.Abp.EntityFrameworkCore;
using AbpVnext_Module.DBContext;
using Ebusiness_Domain.Model;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.EntityFrameworkCore.Internal;

namespace AbpVnext_Module.Repository
{
    /// <summary>
    /// 使用Abp仓储层
    /// </summary>
    [Dependency(ServiceLifetime.Transient)]
    public class ProductImageRepository : EfCoreRepository<ProjectDbContext, ProductImage, int>, IProductImageRepository
    {
        public ProductImageRepository(IDbContextProvider<ProjectDbContext> dbContextProvider) : base(dbContextProvider)
        {
            
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="id"></param>
        /// <param name="includeDetails"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public override async Task<ProductImage> GetAsync(int id, bool includeDetails = true, CancellationToken cancellationToken = default)
        {
            ProductImage productImage = (await GetQueryableAsync()).Include(x => x.ProductImageOrders).First(x => x.Id == id);
            return productImage;
        }

        /// <summary>
        /// 添加
        /// </summary>
        /// <param name="entity"></param>
        /// <param name="autoSave"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public override async Task<ProductImage> InsertAsync(ProductImage entity, bool autoSave = false, CancellationToken cancellationToken = default)
        {
            //var t = await GetDbContextAsync();
            //t.productImages.Add(entity);
            return await base.InsertAsync(entity, autoSave, cancellationToken);
        }

        /// <summary>
        /// 分页
        /// </summary>
        /// <param name="skipCount"></param>
        /// <param name="maxResultCount"></param>
        /// <param name="sorting"></param>
        /// <param name="includeDetails"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public override Task<List<ProductImage>> GetPagedListAsync(int skipCount, int maxResultCount, string sorting, bool includeDetails = false, CancellationToken cancellationToken = default)
        {

            return base.GetPagedListAsync(skipCount, maxResultCount, sorting, includeDetails, cancellationToken);
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="includeDetails"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public override Task<List<ProductImage>> GetListAsync(bool includeDetails = false, CancellationToken cancellationToken = default)
        {
            return base.GetListAsync(includeDetails, cancellationToken);
        }

        /// <summary>
        /// 修改
        /// </summary>
        /// <param name="entity"></param>
        /// <param name="autoSave"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public override async Task<ProductImage> UpdateAsync(ProductImage entity, bool autoSave = false, CancellationToken cancellationToken = default)
        {
            ProjectDbContext projectDbContext = await GetDbContextAsync();
            projectDbContext.Update(entity);
            await projectDbContext.SaveChangesAsync(cancellationToken);
            //ProductImage productImage = await base.UpdateAsync(entity);
            await SaveChangesAsync(default);
            return entity;
        }

        public override async Task DeleteAsync(int id, bool autoSave = false, CancellationToken cancellationToken = default)
        {
            ProductImage productImage = (await GetQueryableAsync()).Include(x => x.ProductImageOrders).First(x => x.Id == id);
            var image = productImage.ProductImageOrders.FirstOrDefault();
            productImage.ProductImageOrders.Remove(image);
            await SaveChangesAsync(default);

        }


        ///// <summary>
        ///// 
        ///// </summary>
        ///// <param name="entity"></param>
        ///// <param name="autoSave"></param>
        ///// <param name="cancellationToken"></param>
        ///// <returns></returns>
        //public override async Task<ProductImage> InsertAsync(ProductImage entity, bool autoSave = false, CancellationToken cancellationToken = default)
        //{
        //    return await base.InsertAsync(entity, autoSave, cancellationToken);
        //}

        /// <summary>
        /// 
        /// </summary>
        /// <param name="productImagePageDto"></param>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public async Task<List<ProductImage>> GetPagedListAsync(ProductImagePagesDto productImagePageDto)
        {
            var context = await GetDbContextAsync();
            //context.ProductImageOrder.AddAsync();
            //var tarns = await context.Database.BeginTransactionAsync();
            //await tarns.CommitAsync();
            //await tarns.RollbackAsync();
            //linq 连接查询
            //var result = from image in context.productImages
            //             join imageorder in context.ProductImageOrder on image.Id equals imageorder.ProductImageId into demp
            //             from emp in demp.DefaultIfEmpty()
            //             where emp.ProductImageId == 124
            //             //join task in context.ProductImageOrder on emp.ProductImageId equals task.ProductImageId into de
            //             //from fe in de.DefaultIfEmpty() //左连接查询
            //             //where fe.ProductImageId == 124
            //             select new
            //             {
            //                 Url = image.Url,
            //                 Descript = emp.Descript
            //             };

            //linq 查询
            var results = from image in context.productImages
                          join imageorder in context.ProductImageOrder on image.Id equals imageorder.ProductImageId into demp
                          from emp in demp.DefaultIfEmpty()
                          //where (1 != 1 ? emp.Id == 1 : emp.ProductImageId == 124) 
                          //where image.TenantId == productImagePageDto.Guid
                          //join task in context.ProductImageOrder on emp.ProductImageId equals task.ProductImageId into de
                          //from fe in  de.DefaultIfEmpty() //左连接查询
                          select new
                          {
                              Url = image.Url,
                              Descript = emp.Descript
                          };
            var count = await results.CountAsync();
            /// 只读场景启用无跟踪查询‌
            var results111 = results.Skip(0).Take(10).AsTracking().ToList();



            //分页查询 显示join查询
            {
                //context.productImages.Include(x => x.ProductImageOrders).Take(count).ToList();

                //SELECT `p`.`Url` AS `name`, `t`.`Descript` AS `descrpt`, `p1`.`Descript` AS `dex`
                //FROM `productImages` AS `p`
                //INNER JOIN(
                //    SELECT `p0`.`Id`, `p0`.`Descript`, `p0`.`ProductImageId`
                //    FROM `ProductImageOrder` AS `p0`
                //    WHERE `p0`.`Id` = 1
                //) AS `t` ON `p`.`Id` = `t`.`ProductImageId`
                //INNER JOIN `ProductImageOrder` AS `p1` ON `t`.`Id` = `p1`.`Id`
                //WHERE `p`.`Id` = 14
                //LIMIT @__p_0 OFFSET @__p_0
                var xws = context.productImages.Join(context.ProductImageOrder.
                    WhereIf(1 == 1, x => x.Id == 1), x => x.Id, y => y.ProductImageId, (x, y) => new
                    {
                        image = x,
                        imgaeorder = y
                    })
                .Join(context.ProductImageOrder, x => x.imgaeorder.Id, y => y.Id, (x, y) => new
                {
                    xx = x.image,
                    yy = x.imgaeorder,
                    zz = y,
                }).
                // 添加查询条件（例如：筛选已上架商品）
                WhereIf(1 == 1, x => x.xx.Id == 14).
                // 投影选择所需字段
                Select(x => new
                {
                    name = x.xx.Url,
                    descrpt = x.yy.Descript,
                    dex = x.zz.Descript
                });

                var xwsCount = xws.Count();
                var xwslist = xws.Skip(2).Take(2).ToList();
            }
            //分页查询

            {
                //SELECT `p`.`Id` AS `imageId`, `t`.`Id` AS `imgaeorderId`, `p`.`Url` AS `url`, `t`.`Descript`, `p1`.`Descript` AS `x222Descript`, `p1`.`Id` AS `x222ID`
                //FROM `productImages` AS `p`
                //INNER JOIN(
                //    SELECT `p0`.`Id`, `p0`.`Descript`, `p0`.`ProductImageId`
                //    FROM `ProductImageOrder` AS `p0`
                //    WHERE `p0`.`Id` = 1
                //) AS `t` ON `p`.`Id` = `t`.`ProductImageId`
                //INNER JOIN `ProductImageOrder` AS `p1` ON `t`.`Id` = `p1`.`Id`
                //WHERE `p`.`Id` = 14
                //LIMIT @__p_0 OFFSET @__p_0


                //var xws = context.productImages.Join(context.ProductImageOrder.
                //    WhereIf(1 == 1, x => x.Id == 1), x => x.Id, y => y.ProductImageId, (x, y) => new
                //    {
                //        imageId = x.Id,
                //        imgaeorderId = y.Id,
                //        url = x.Url,
                //        Descript = y.Descript
                //    })
                //.Join(context.ProductImageOrder, x => x.imgaeorderId, y => y.Id, (x, y) => new
                //{
                //    imageId = x.imageId,
                //    imgaeorderId = x.imgaeorderId,
                //    url = x.url,
                //    Descript = x.Descript,
                //    x222Descript = y.Descript,
                //    x222ID = y.Id
                //}).
                ////// 添加查询条件（例如：筛选已上架商品）
                //WhereIf(1 == 1, x => x.imageId == 14).Select(x => new  //// 投影选择所需字段
                //{
                //    imageId = x.imageId,
                //    imgaeorderId = x.imgaeorderId,
                //    url = x.url,
                //    Descript = x.Descript,
                //    x222Descript = x.x222Descript,
                //    x222ID = x.x222ID
                //});

                //var xwsCount = xws.Count();
                //var xwslist = xws.Skip(2).Take(2).ToList();
            }


            //分页查询 linq查询
            var results4 = from image in context.productImages
                           join imageorder in context.ProductImageOrder on image.Id equals imageorder.ProductImageId into demp
                           from emp in demp.DefaultIfEmpty()
                               //join task in context.ProductImageOrder on emp.ProductImageId equals task.ProductImageId into de
                               //from fe in  de.DefaultIfEmpty() //左连接查询
                           orderby image.Id
                           select new
                           {
                               Url = image.Url,
                               Descript = emp.Descript
                           };

            var productImages2 = (await GetQueryableAsync()).
                   //Include(x => x.ProductImageOrders.WhereIf(true, x => x.Descript == "4")).
                   //WhereIf(productImagePageDto.Url != null, x => x.Url.Contains(productImagePageDto.Url)).
                   Include(x => x.ProductImageOrders).
                   //ThenInclude(x => x.ProductImageOrders).     //多表关联查询
                   //ThenInclude(x => x.ProductImageOrders).
                   Where(x => x.Id == productImagePageDto.Id)
                   //Where(x => x.ProductImageOrders.Any(x => x.Id == 126))
                   .Skip(productImagePageDto.SkipCount).
                   Take(productImagePageDto.MaxResultCount).OrderBy(productImagePageDto.Sorting)
                   .Select(o => new
                   {
                       Id = o.Id,
                       url = o.Url,
                       items = o.ProductImageOrders.Select(x => x.Id),
                       item2 = o.ProductImageOrders,
                       //多张表投影查询
                       //item3 = o.ProductImageOrders.Select(x => new { 
                       //    Id = x.Id,
                       //    descrt = x.Descript,
                       //    orders = x.ProductImageOrders.Select(s => new { 
                       //        produc = s.Id,
                       //        pro= s.ProductImage
                       //    })
                       //})
                   }).ToList();

            //导航属性查询    
            List<ProductImage> productImages = (await GetQueryableAsync()).
                Include(x => x.ProductImageOrders.Where(x => x.Descript == "4")).
                WhereIf(productImagePageDto.Url != null, x => x.Url.Contains(productImagePageDto.Url)).
                Where(x => x.Id == productImagePageDto.Id)
                //Where(x => x.ProductImageOrders.Any(x => x.Id == 126))
                .Skip(productImagePageDto.SkipCount).
                Take(productImagePageDto.MaxResultCount).OrderBy(productImagePageDto.Sorting).ToList();
            return productImages;
        }
    }
}
